diff --git a/drivers/mtd/nand/nand_util.c b/drivers/mtd/nand/nand_util.c
index 9fe4866..02fe914 100644
--- a/drivers/mtd/nand/nand_util.c
+++ b/drivers/mtd/nand/nand_util.c
@@ -248,586 +248,6 @@
 };
 #endif
 
-
-/**
- * nand_fill_oob - [Internal] Transfer client buffer to oob
- * @chip:	nand chip structure
- * @oob:	oob data buffer
- * @ops:	oob ops structure
- *
- * Copied from nand_base.c
- */
-static uint8_t *nand_fill_oob(struct nand_chip *chip, uint8_t *oob,
-				  struct mtd_oob_ops *ops)
-{
-	size_t len = ops->ooblen;
-
-	switch(ops->mode) {
-
-	case MTD_OOB_PLACE:
-	case MTD_OOB_RAW:
-		memcpy(chip->oob_poi + ops->ooboffs, oob, len);
-		return oob + len;
-
-	case MTD_OOB_AUTO: {
-		struct nand_oobfree *free = chip->ecc.layout->oobfree;
-		uint32_t boffs = 0, woffs = ops->ooboffs;
-		size_t bytes = 0;
-
-		for(; free->length && len; free++, len -= bytes) {
-			/* Write request not from offset 0 ? */
-			if (unlikely(woffs)) {
-				if (woffs >= free->length) {
-					woffs -= free->length;
-					continue;
-				}
-				boffs = free->offset + woffs;
-				bytes = min_t(size_t, len,
-					      (free->length - woffs));
-				woffs = 0;
-			} else {
-				bytes = min_t(size_t, len, free->length);
-				boffs = free->offset;
-			}
-			memcpy(chip->oob_poi + boffs, oob, bytes);
-			oob += bytes;
-		}
-		return oob;
-	}
-	default:
-		BUG();
-	}
-	return NULL;
-}
-
-#define NOTALIGNED(x)	(x & (chip->subpagesize - 1)) != 0
-
-
-/* copied from nand_base.c: nand_do_write_ops()
- * Only very small changes
- */
-int nand_write_opts(nand_info_t *mtd, loff_t to, mtd_oob_ops_t *ops)
-{
-	int chipnr, realpage, page, blockmask, column;
-	struct nand_chip *chip = mtd->priv;
-	uint32_t writelen = ops->len;
-	uint8_t *oob = ops->oobbuf;
-	uint8_t *buf = ops->datbuf;
-	int ret, subpage;
-
-	ops->retlen = 0;
-	if (!writelen)
-		return 0;
-
-	printk("nand_write_opts: to: 0x%08x, ops->len: 0x%08x\n", to, ops->len);
-
-	/* reject writes, which are not page aligned */
-	if (NOTALIGNED(to) || NOTALIGNED(ops->len)) {
-		printk(KERN_NOTICE "nand_write: "
-		       "Attempt to write not page aligned data\n");
-		return -EINVAL;
-	}
-
-	column = to & (mtd->writesize - 1);
-	subpage = column || (writelen & (mtd->writesize - 1));
-
-	if (subpage && oob) {
-		printk(KERN_NOTICE "nand_write: "
-		       "Attempt to write oob to subpage\n");
-		return -EINVAL;
-	}
-
-	chipnr = (int)(to >> chip->chip_shift);
-	chip->select_chip(mtd, chipnr);
-
-	/* XXX U-BOOT XXX */
-#if 0
-	/* Check, if it is write protected */
-	if (nand_check_wp(mtd))
-		return -EIO;
-#endif
-
-	realpage = (int)(to >> chip->page_shift);
-	page = realpage & chip->pagemask;
-	blockmask = (1 << (chip->phys_erase_shift - chip->page_shift)) - 1;
-
-	/* Invalidate the page cache, when we write to the cached page */
-	if (to <= (chip->pagebuf << chip->page_shift) &&
-	    (chip->pagebuf << chip->page_shift) < (to + ops->len))
-		chip->pagebuf = -1;
-
-	/* If we're not given explicit OOB data, let it be 0xFF */
-	if (likely(!oob)) {
-		printf("!oob, writing %d bytes with 0xff to chip->oob_poi (0x%08x)\n", mtd->oobsize, chip->oob_poi);
-		memset(chip->oob_poi, 0xff, mtd->oobsize);
-	}
-
-	while(1) {
-		int bytes = mtd->writesize;
-		int cached = writelen > bytes && page != blockmask;
-		uint8_t *wbuf = buf;
-
-		/* Partial page write ? */
-		if (unlikely(column || writelen < (mtd->writesize - 1))) {
-			cached = 0;
-			bytes = min_t(int, bytes - column, (int) writelen);
-			chip->pagebuf = -1;
-			memset(chip->buffers->databuf, 0xff, mtd->writesize);
-			memcpy(&chip->buffers->databuf[column], buf, bytes);
-			wbuf = chip->buffers->databuf;
-		}
-
-		if (unlikely(oob))
-			oob = nand_fill_oob(chip, oob, ops);
-
-		ret = chip->write_page(mtd, chip, wbuf, page, cached,
-				       (ops->mode == MTD_OOB_RAW));
-		if (ret)
-			break;
-
-		writelen -= bytes;
-		if (!writelen)
-			break;
-
-		column = 0;
-		buf += bytes;
-		realpage++;
-
-		page = realpage & chip->pagemask;
-		/* Check, if we cross a chip boundary */
-		if (!page) {
-			chipnr++;
-			chip->select_chip(mtd, -1);
-			chip->select_chip(mtd, chipnr);
-		}
-	}
-
-	ops->retlen = ops->len - writelen;
-	if (unlikely(oob))
-		ops->oobretlen = ops->ooblen;
-	return ret;
-}
-
-/* XXX U-BOOT XXX */
-#if 0
-/**
- * nand_write_opts: - write image to NAND flash with support for various options
- *
- * @param meminfo	NAND device to erase
- * @param opts		write options (@see nand_write_options)
- * @return		0 in case of success
- *
- * This code is ported from nandwrite.c from Linux mtd utils by
- * Steven J. Hill and Thomas Gleixner.
- */
-int nand_write_opts(nand_info_t *meminfo, const nand_write_options_t *opts)
-{
-	int imglen = 0;
-	int pagelen;
-	int baderaseblock;
-	int blockstart = -1;
-	loff_t offs;
-	int readlen;
-	int ecclayoutchanged = 0;
-	int percent_complete = -1;
-	struct nand_ecclayout old_ecclayout;
-	ulong mtdoffset = opts->offset;
-	ulong erasesize_blockalign;
-	u_char *buffer = opts->buffer;
-	size_t written;
-	int result;
-
-	if (opts->pad && opts->writeoob) {
-		printf("Can't pad when oob data is present.\n");
-		return -1;
-	}
-
-	/* set erasesize to specified number of blocks - to match
-	 * jffs2 (virtual) block size */
-	if (opts->blockalign == 0) {
-		erasesize_blockalign = meminfo->erasesize;
-	} else {
-		erasesize_blockalign = meminfo->erasesize * opts->blockalign;
-	}
-
-	/* make sure device page sizes are valid */
-	if (!(meminfo->oobsize == 16 && meminfo->writesize == 512)
-	    && !(meminfo->oobsize == 8 && meminfo->writesize == 256)
-	    && !(meminfo->oobsize == 64 && meminfo->writesize == 2048)) {
-		printf("Unknown flash (not normal NAND)\n");
-		return -1;
-	}
-
-	/* read the current oob info */
-	memcpy(&old_ecclayout, &meminfo->ecclayout, sizeof(old_ecclayout));
-
-	/* write without ecc? */
-	if (opts->noecc) {
-		memcpy(&meminfo->ecclayout, &none_ecclayout,
-		       sizeof(meminfo->ecclayout));
-		ecclayoutchanged = 1;
-	}
-
-	/* autoplace ECC? */
-	if (opts->autoplace && (old_ecclayout.useecc != MTD_NANDECC_AUTOPLACE)) {
-
-		memcpy(&meminfo->ecclayout, &autoplace_ecclayout,
-		       sizeof(meminfo->ecclayout));
-		ecclayoutchanged = 1;
-	}
-
-	/* force OOB layout for jffs2 or yaffs? */
-	if (opts->forcejffs2 || opts->forceyaffs) {
-		struct nand_ecclayout *oobsel =
-			opts->forcejffs2 ? &jffs2_ecclayout : &yaffs_ecclayout;
-
-		if (meminfo->oobsize == 8) {
-			if (opts->forceyaffs) {
-				printf("YAFSS cannot operate on "
-				       "256 Byte page size\n");
-				goto restoreoob;
-			}
-			/* Adjust number of ecc bytes */
-			jffs2_ecclayout.eccbytes = 3;
-		}
-
-		memcpy(&meminfo->ecclayout, oobsel, sizeof(meminfo->ecclayout));
-	}
-
-	/* get image length */
-	imglen = opts->length;
-	pagelen = meminfo->writesize
-		+ ((opts->writeoob != 0) ? meminfo->oobsize : 0);
-
-	/* check, if file is pagealigned */
-	if ((!opts->pad) && ((imglen % pagelen) != 0)) {
-		printf("Input block length is not page aligned\n");
-		goto restoreoob;
-	}
-
-	/* check, if length fits into device */
-	if (((imglen / pagelen) * meminfo->writesize)
-	     > (meminfo->size - opts->offset)) {
-		printf("Image %d bytes, NAND page %d bytes, "
-		       "OOB area %u bytes, device size %u bytes\n",
-		       imglen, pagelen, meminfo->writesize, meminfo->size);
-		printf("Input block does not fit into device\n");
-		goto restoreoob;
-	}
-
-	if (!opts->quiet)
-		printf("\n");
-
-	/* get data from input and write to the device */
-	while (imglen && (mtdoffset < meminfo->size)) {
-
-		WATCHDOG_RESET ();
-
-		/*
-		 * new eraseblock, check for bad block(s). Stay in the
-		 * loop to be sure if the offset changes because of
-		 * a bad block, that the next block that will be
-		 * written to is also checked. Thus avoiding errors if
-		 * the block(s) after the skipped block(s) is also bad
-		 * (number of blocks depending on the blockalign
-		 */
-		while (blockstart != (mtdoffset & (~erasesize_blockalign+1))) {
-			blockstart = mtdoffset & (~erasesize_blockalign+1);
-			offs = blockstart;
-			baderaseblock = 0;
-
-			/* check all the blocks in an erase block for
-			 * bad blocks */
-			do {
-				int ret = meminfo->block_isbad(meminfo, offs);
-
-				if (ret < 0) {
-					printf("Bad block check failed\n");
-					goto restoreoob;
-				}
-				if (ret == 1) {
-					baderaseblock = 1;
-					if (!opts->quiet)
-						printf("\rBad block at 0x%lx "
-						       "in erase block from "
-						       "0x%x will be skipped\n",
-						       (long) offs,
-						       blockstart);
-				}
-
-				if (baderaseblock) {
-					mtdoffset = blockstart
-						+ erasesize_blockalign;
-				}
-				offs +=	 erasesize_blockalign
-					/ opts->blockalign;
-			} while (offs < blockstart + erasesize_blockalign);
-		}
-
-		readlen = meminfo->writesize;
-		if (opts->pad && (imglen < readlen)) {
-			readlen = imglen;
-			memset(data_buf + readlen, 0xff,
-			       meminfo->writesize - readlen);
-		}
-
-		/* read page data from input memory buffer */
-		memcpy(data_buf, buffer, readlen);
-		buffer += readlen;
-
-		if (opts->writeoob) {
-			/* read OOB data from input memory block, exit
-			 * on failure */
-			memcpy(oob_buf, buffer, meminfo->oobsize);
-			buffer += meminfo->oobsize;
-
-			/* write OOB data first, as ecc will be placed
-			 * in there*/
-			result = meminfo->write_oob(meminfo,
-						    mtdoffset,
-						    meminfo->oobsize,
-						    &written,
-						    (unsigned char *)
-						    &oob_buf);
-
-			if (result != 0) {
-				printf("\nMTD writeoob failure: %d\n",
-				       result);
-				goto restoreoob;
-			}
-			imglen -= meminfo->oobsize;
-		}
-
-		/* write out the page data */
-		result = meminfo->write(meminfo,
-					mtdoffset,
-					meminfo->writesize,
-					&written,
-					(unsigned char *) &data_buf);
-
-		if (result != 0) {
-			printf("writing NAND page at offset 0x%lx failed\n",
-			       mtdoffset);
-			goto restoreoob;
-		}
-		imglen -= readlen;
-
-		if (!opts->quiet) {
-			unsigned long long n = (unsigned long long)
-				 (opts->length-imglen) * 100;
-			int percent;
-
-			do_div(n, opts->length);
-			percent = (int)n;
-
-			/* output progress message only at whole percent
-			 * steps to reduce the number of messages printed
-			 * on (slow) serial consoles
-			 */
-			if (percent != percent_complete) {
-				printf("\rWriting data at 0x%lx "
-				       "-- %3d%% complete.",
-				       mtdoffset, percent);
-				percent_complete = percent;
-			}
-		}
-
-		mtdoffset += meminfo->writesize;
-	}
-
-	if (!opts->quiet)
-		printf("\n");
-
-restoreoob:
-	if (ecclayoutchanged) {
-		memcpy(&meminfo->ecclayout, &old_ecclayout,
-		       sizeof(meminfo->ecclayout));
-	}
-
-	if (imglen > 0) {
-		printf("Data did not fit into device, due to bad blocks\n");
-		return -1;
-	}
-
-	/* return happy */
-	return 0;
-}
-
-/**
- * nand_read_opts: - read image from NAND flash with support for various options
- *
- * @param meminfo	NAND device to erase
- * @param opts		read options (@see struct nand_read_options)
- * @return		0 in case of success
- *
- */
-int nand_read_opts(nand_info_t *meminfo, const nand_read_options_t *opts)
-{
-	int imglen = opts->length;
-	int pagelen;
-	int baderaseblock;
-	int blockstart = -1;
-	int percent_complete = -1;
-	loff_t offs;
-	size_t readlen;
-	ulong mtdoffset = opts->offset;
-	u_char *buffer = opts->buffer;
-	int result;
-
-	/* make sure device page sizes are valid */
-	if (!(meminfo->oobsize == 16 && meminfo->writesize == 512)
-	    && !(meminfo->oobsize == 8 && meminfo->writesize == 256)
-	    && !(meminfo->oobsize == 64 && meminfo->writesize == 2048)) {
-		printf("Unknown flash (not normal NAND)\n");
-		return -1;
-	}
-
-	pagelen = meminfo->writesize
-		+ ((opts->readoob != 0) ? meminfo->oobsize : 0);
-
-	/* check, if length is not larger than device */
-	if (((imglen / pagelen) * meminfo->writesize)
-	     > (meminfo->size - opts->offset)) {
-		printf("Image %d bytes, NAND page %d bytes, "
-		       "OOB area %u bytes, device size %u bytes\n",
-		       imglen, pagelen, meminfo->writesize, meminfo->size);
-		printf("Input block is larger than device\n");
-		return -1;
-	}
-
-	if (!opts->quiet)
-		printf("\n");
-
-	/* get data from input and write to the device */
-	while (imglen && (mtdoffset < meminfo->size)) {
-
-		WATCHDOG_RESET ();
-
-		/*
-		 * new eraseblock, check for bad block(s). Stay in the
-		 * loop to be sure if the offset changes because of
-		 * a bad block, that the next block that will be
-		 * written to is also checked. Thus avoiding errors if
-		 * the block(s) after the skipped block(s) is also bad
-		 * (number of blocks depending on the blockalign
-		 */
-		while (blockstart != (mtdoffset & (~meminfo->erasesize+1))) {
-			blockstart = mtdoffset & (~meminfo->erasesize+1);
-			offs = blockstart;
-			baderaseblock = 0;
-
-			/* check all the blocks in an erase block for
-			 * bad blocks */
-			do {
-				int ret = meminfo->block_isbad(meminfo, offs);
-
-				if (ret < 0) {
-					printf("Bad block check failed\n");
-					return -1;
-				}
-				if (ret == 1) {
-					baderaseblock = 1;
-					if (!opts->quiet)
-						printf("\rBad block at 0x%lx "
-						       "in erase block from "
-						       "0x%x will be skipped\n",
-						       (long) offs,
-						       blockstart);
-				}
-
-				if (baderaseblock) {
-					mtdoffset = blockstart
-						+ meminfo->erasesize;
-				}
-				offs +=	 meminfo->erasesize;
-
-			} while (offs < blockstart + meminfo->erasesize);
-		}
-
-
-		/* read page data to memory buffer */
-		result = meminfo->read(meminfo,
-				       mtdoffset,
-				       meminfo->writesize,
-				       &readlen,
-				       (unsigned char *) &data_buf);
-
-		if (result != 0) {
-			printf("reading NAND page at offset 0x%lx failed\n",
-			       mtdoffset);
-			return -1;
-		}
-
-		if (imglen < readlen) {
-			readlen = imglen;
-		}
-
-		memcpy(buffer, data_buf, readlen);
-		buffer += readlen;
-		imglen -= readlen;
-
-		if (opts->readoob) {
-			result = meminfo->read_oob(meminfo,
-						   mtdoffset,
-						   meminfo->oobsize,
-						   &readlen,
-						   (unsigned char *)
-						   &oob_buf);
-
-			if (result != 0) {
-				printf("\nMTD readoob failure: %d\n",
-				       result);
-				return -1;
-			}
-
-
-			if (imglen < readlen) {
-				readlen = imglen;
-			}
-
-			memcpy(buffer, oob_buf, readlen);
-
-			buffer += readlen;
-			imglen -= readlen;
-		}
-
-		if (!opts->quiet) {
-			unsigned long long n = (unsigned long long)
-				 (opts->length-imglen) * 100;
-			int percent;
-
-			do_div(n, opts->length);
-			percent = (int)n;
-
-			/* output progress message only at whole percent
-			 * steps to reduce the number of messages printed
-			 * on (slow) serial consoles
-			 */
-			if (percent != percent_complete) {
-			if (!opts->quiet)
-				printf("\rReading data from 0x%lx "
-				       "-- %3d%% complete.",
-				       mtdoffset, percent);
-				percent_complete = percent;
-			}
-		}
-
-		mtdoffset += meminfo->writesize;
-	}
-
-	if (!opts->quiet)
-		printf("\n");
-
-	if (imglen > 0) {
-		printf("Could not read entire image due to bad blocks\n");
-		return -1;
-	}
-
-	/* return happy */
-	return 0;
-}
-#endif
-
 /* XXX U-BOOT XXX */
 #if 0
 /******************************************************************************
@@ -1007,4 +427,184 @@
 }
 #endif
 
-#endif
+/**
+ * get_len_incl_bad
+ *
+ * Check if length including bad blocks fits into device.
+ *
+ * @param nand NAND device
+ * @param offset offset in flash
+ * @param length image length
+ * @return image length including bad blocks
+ */
+static size_t get_len_incl_bad (nand_info_t *nand, size_t offset,
+                                const size_t length)
+{
+	size_t len_incl_bad = 0;
+	size_t len_excl_bad = 0;
+	size_t block_len;
+
+	while (len_excl_bad < length) {
+		block_len = nand->erasesize - (offset & (nand->erasesize - 1));
+
+		if (!nand_block_isbad (nand, offset & ~(nand->erasesize - 1)))
+			len_excl_bad += block_len;
+
+		len_incl_bad += block_len;
+		offset       += block_len;
+
+		if ((offset + len_incl_bad) >= nand->size)
+			break;
+	}
+
+	return len_incl_bad;
+}
+
+/**
+ * nand_write_skip_bad:
+ *
+ * Write image to NAND flash.
+ * Blocks that are marked bad are skipped and the is written to the next
+ * block instead as long as the image is short enough to fit even after
+ * skipping the bad blocks.
+ *
+ * @param nand  	NAND device
+ * @param offset	offset in flash
+ * @param length	buffer length
+ * @param buf           buffer to read from
+ * @return		0 in case of success
+ */
+int nand_write_skip_bad(nand_info_t *nand, size_t offset, size_t *length,
+                        u_char *buffer)
+{
+	int rval;
+	size_t left_to_write = *length;
+	size_t len_incl_bad;
+	u_char *p_buffer = buffer;
+
+	/* Reject writes, which are not page aligned */
+	if ((offset & (nand->writesize - 1)) != 0 ||
+	    (*length & (nand->writesize - 1)) != 0) {
+		printf ("Attempt to write non page aligned data\n");
+		return -EINVAL;
+	}
+
+	len_incl_bad = get_len_incl_bad (nand, offset, *length);
+
+	if ((offset + len_incl_bad) >= nand->size) {
+		printf ("Attempt to write outside the flash area\n");
+		return -EINVAL;
+	}
+
+	if (len_incl_bad == *length) {
+		rval = nand_write (nand, offset, length, buffer);
+		if (rval != 0) {
+			printf ("NAND write to offset %x failed %d\n",
+			        offset, rval);
+			return rval;
+		}
+	}
+
+	while (left_to_write > 0) {
+		size_t block_offset = offset & (nand->erasesize - 1);
+		size_t write_size;
+
+		if (nand_block_isbad (nand, offset & ~(nand->erasesize - 1))) {
+			printf ("Skip bad block 0x%08x\n",
+				offset & ~(nand->erasesize - 1));
+			offset += nand->erasesize - block_offset;
+			continue;
+		}
+
+		if (left_to_write < (nand->erasesize - block_offset))
+			write_size = left_to_write;
+		else
+			write_size = nand->erasesize - block_offset;
+
+		rval = nand_write (nand, offset, &write_size, p_buffer);
+		if (rval != 0) {
+			printf ("NAND write to offset %x failed %d\n",
+			        offset, rval);
+			*length -= left_to_write;
+			return rval;
+		}
+
+		left_to_write -= write_size;
+		offset        += write_size;
+		p_buffer      += write_size;
+	}
+
+	return 0;
+}
+
+/**
+ * nand_read_skip_bad:
+ *
+ * Read image from NAND flash.
+ * Blocks that are marked bad are skipped and the next block is readen
+ * instead as long as the image is short enough to fit even after skipping the
+ * bad blocks.
+ *
+ * @param nand NAND device
+ * @param offset offset in flash
+ * @param length buffer length, on return holds remaining bytes to read
+ * @param buffer buffer to write to
+ * @return 0 in case of success
+ */
+int nand_read_skip_bad(nand_info_t *nand, size_t offset, size_t *length,
+		       u_char *buffer)
+{
+	int rval;
+	size_t left_to_read = *length;
+	size_t len_incl_bad;
+	u_char *p_buffer = buffer;
+
+	len_incl_bad = get_len_incl_bad (nand, offset, *length);
+
+	if ((offset + len_incl_bad) >= nand->size) {
+		printf ("Attempt to read outside the flash area\n");
+		return -EINVAL;
+	}
+
+	if (len_incl_bad == *length) {
+		rval = nand_read (nand, offset, length, buffer);
+		if (rval != 0) {
+			printf ("NAND read from offset %x failed %d\n",
+			        offset, rval);
+			return rval;
+		}
+	}
+
+	while (left_to_read > 0) {
+		size_t block_offset = offset & (nand->erasesize - 1);
+		size_t read_length;
+
+		if (nand_block_isbad (nand, offset & ~(nand->erasesize - 1))) {
+			printf ("Skipping bad block 0x%08x\n",
+				offset & ~(nand->erasesize - 1));
+			offset += nand->erasesize - block_offset;
+			continue;
+		}
+
+		if (left_to_read < (nand->erasesize - block_offset))
+			read_length = left_to_read;
+		else
+			read_length = nand->erasesize - block_offset;
+
+		rval = nand_read (nand, offset, &read_length, p_buffer);
+		if (rval != 0) {
+			printf ("NAND read from offset %x failed %d\n",
+			        offset, rval);
+			*length -= left_to_read;
+			return rval;
+		}
+
+		left_to_read -= read_length;
+		offset       += read_length;
+		p_buffer     += read_length;
+	}
+
+	return 0;
+}
+
+#endif /* defined(CONFIG_CMD_NAND) && !defined(CFG_NAND_LEGACY) */
